<script>

import EmployeeArchives from './components/EmployeeArchives'
import CompanyArchives from './components/CompanyArchives'
import OtherArchives from './components/OtherArchives/index.vue'
import WorkExperience from './components/WorkExperience'
import Certificate from './components/Certificate'
import EducationalExperience from './components/EducationalExperience'
import FamilyMember from './components/FamilyMember'
import SignedAgreements from './components/SignedAgreements'
import SingleImage from '@/components/Upload/SingleImage'
import Courses from './components/Courses'
import FieldsModifyHistory from './components/FieldsModifyHistory/index.vue'

import {
  getNation,
  getMarriage,
  getSchool,
  getPolitic,
  getPosition,
  getEducation
} from '@/api/basic'

import {
  getUser
} from '@/api/personnel'

import { getFieldsList } from '@/api/customFields'

import { getPersonnelDetails, administratorModifyFile, exportEntry } from '@/api/v2/personnel'

import { get, value, isString, atLeast, last, isNotBlank } from '@/utils/kris_utils'
import { fieldConfigs, FieldType } from './lib/built_in_field'
import { cloneDeep } from 'lodash-es'
import dayjs from 'dayjs'

export const fieldID = {
  EDU_EXP_ID: 16,
  WORK_EXP_ID: 15,
  CERTIFICATE_ID: 37,
  FAMILY_MEMBER_ID: 18
}

export default {
  components: {
    EmployeeArchives,
    CompanyArchives,
    OtherArchives,
    WorkExperience,
    EducationalExperience,
    FamilyMember,
    SignedAgreements,
    SingleImage,
    Certificate,
    Courses,
    FieldsModifyHistory
  },
  props: {},
  data() {
    return {
      userID: null,
      isEditing: false,
      isLoading: false,
      isSubmitting: false,

      fieldList: null,

      rawProfileData: null,

      // 员工档案
      employeeDetails: {
        draft: null,
        backup: null,
        isSubmitting: false
      },

      // 公司档案
      companyDetails: {
        draft: null,
        backup: null,
        isSubmitting: false
      },

      // 自定义字段
      customField: {
        draft: null,
        backup: null,
        isSubmitting: false,
        fieldConfig: null
      },

      familyMember: {
        isSubmitting: false
      },
      workExperience: {
        isSubmitting: false
      },
      educationalExperience: {
        isSubmitting: false
      },
      certList: {
        isSubmitting: false
      },

      exportProfile: {
        loading: false
      },
      updateIDCardDialog: {
        visible: false,
        idcardBackCache: null,
        idcardFrontCache: null,
        applyToProfile: false
      },

      uploadDialog: {
        visible: false,
        type: null,
        result: null
      },

      // ---------- sep line ----------
      nations: [],
      marriageStatuses: [],
      politics: [],
      posts: [],
      educationalLevel: [],
      schools: []
    }
  },
  computed: {
    fieldCfgs() {
      const result = {
        byRawField: new Map(),
        byField: new Map()
      }

      for (const i in fieldConfigs) {
        const field = fieldConfigs[i]

        result.byRawField.set(field['mapTo'], field)
        result.byField.set(field['field'], field)
      }

      return result
    },
    // 婚姻状态选项
    marriageStatusesOptions() {
      return this.marriageStatuses.map(item => {
        return {
          label: item.name,
          value: item.id
        }
      })
    },

    // 学历选项
    educationalLevelOptions() {
      return this.educationalLevel.map(item => {
        return {
          label: item.name,
          value: item.id
        }
      })
    },

    // 政治面貌
    politicsOptions() {
      return this.politics.map(item => {
        return {
          label: item.name,
          value: item.id
        }
      })
    },

    // 民族
    nationOptions() {
      return this.nations.map(item => {
        return {
          label: item.nation,
          value: item.id
        }
      })
    },

    // 岗位
    postOptions() {
      return this.posts.map(item => {
        return {
          label: item.name,
          value: item.id
        }
      })
    },

    customFieldsFormatter() {
      const values = this.customField.fieldConfig.values()
      const arr = Array.from(values)
      return arr
    }
  },
  created() {
    this.init()
  },
  methods: {
    build() {
      if (!Array.isArray(this.rawProfileData)) { return }

      const tables = {}

      // rawData -> deserialize -> formatter
      const dataMap = new Map()
      const customField = {
        config: new Map(),
        data: {}
      }
      for (const i in this.rawProfileData) {
        const data = this.rawProfileData[i]
        const rawField = get(data, 'field.field', null)

        if (get(data, 'field.class', null) === FieldType.CUSTOM) {
          const fieldCfg = data.field
          let content = data.content
          if (fieldCfg.type === 'date') {
            content = content ? dayjs(content).toDate() : null
          }
          customField.data[fieldCfg.field] = content

          customField.config.set(fieldCfg.field, fieldCfg)
          // customField.config.set(fieldCfg.field, {
          //   id: fieldCfg.id,
          //   field: fieldCfg.field,
          //   name: fieldCfg.name,
          //   type: fieldCfg.type,
          //   table: fieldCfg.table
          // })
        }

        // 这行是给你提示的，就是映射中哪些字段空了，你就补一下
        if (!isNotBlank(rawField)) { throw new Error(`这里是空的，补一下`) }

        dataMap.set(rawField, data)
      }

      this.buildBuiltFields(dataMap, tables)

      tables.customField = customField
      this.convert(tables)
    },
    initFields() {
      const tables = {
        customField: {
          data: {},
          config: new Map()
        }
      }
      const dataMap = new Map()

      this.buildBuiltFields(dataMap, tables)
      this.convert(tables)
    },
    buildBuiltFields(dataMap, tables) {
      // 系统字段就算没有返回也要给 Fallback ，保证字段可以渲染空值 && 防止组件报错
      for (const [k, fieldCfg] of this.fieldCfgs.byField) {
        // fieldCfg 是字段的配置，也就是手写的映射
        const data = dataMap.get(fieldCfg.mapTo) // 字段的数据
        console.log('fieldCfg', k)
        if (atLeast(data, ['domicile_array'])) {
          data.valueType = {
            ...data.valueType,
            domicile_array: data.domicile_array
          }
        }

        let result = null

        // atLeast(data,['']) 这个函数是要求 第二个参数里的key必须存在于这个对象中
        // 这里我就写了基本的几个字段，你可以继续加
        if (atLeast(data, ['content', 'field', 'id'])) {
          result = data.content

          if (typeof fieldCfg['deserialize'] === 'function') {
            result = fieldCfg['deserialize'].apply(this, [fieldCfg, result])
          }

          if (typeof fieldCfg['formatter'] === 'function') {
            result = fieldCfg['formatter'].apply(this, [fieldCfg, result, data.valueType])
          }
        } else {
          // 没数据就设置fallback
          result = fieldCfg.fallback
        }

        if (!(fieldCfg['ofTable'] in tables)) { tables[fieldCfg['ofTable']] = {} }

        tables[fieldCfg['ofTable']][fieldCfg.field] = result
      }
    },
    // 解析数据
    convert(data) {
      const { user_details, user_companys, customField: { data: value, config }} = data
      this.employeeDetails.draft = { ...user_details }
      this.companyDetails.draft = { ...user_companys }
      this.customField.draft = { ...value }
      this.customField.fieldConfig = config
    },

    async refresh() {
      try {
        this.isLoading = true
        await this.sleep(500)
        await this.initData()
        // this.loadData()
        this.isLoading = false
        this.isEditing = false
      } catch (error) {
        this.isLoading = false
        this.$message.error('刷新失败：' + error.message)
      }
    },
    sleep(t) {
      return new Promise(r => setTimeout(r, t))
    },

    // 保存操作

    async savePersonnelProfileV2(params) {
      const result = await administratorModifyFile(params)
        .catch(err => {
          throw new Error('保存员工档案失败', err)
        })
      if (result.code !== 200) {
        throw new Error(value(result, 'message', '保存员工档案失败'))
      }
      return result
    },

    async saveAll() {
      try {
        this.isSubmitting = true
        const params = {
          ...this.buildEmployeeProfileParamsV2(),
          ...this.buildCompanyProfileParamsV2(),
          ...this.buildOtherProfileParams()
        }

        const res = await this.savePersonnelProfileV2({
          field: JSON.stringify(params),
          user_id: this.userID
        })
        this.$message.success(res.message)
        this.refresh()
      } catch (error) {
        this.$message.error(error.message)
      } finally {
        this.isSubmitting = false
      }
    },

    async saveCompanyProfile() {
      try {
        this.companyDetails.isSubmitting = true
        const params = {
          user_id: this.userID,
          field: JSON.stringify(this.buildCompanyProfileParamsV2())
        }
        const result = await this.savePersonnelProfileV2(params)
        this.$message.success(result.message)
        this.refresh()
      } catch (error) {
        this.$message.error(error.message)
      } finally {
        this.companyDetails.isSubmitting = false
      }
    },

    async saveOtherProfile() {
      try {
        this.customField.isSubmitting = true
        const params = {
          user_id: this.userID,
          field: JSON.stringify(this.buildOtherProfileParams())
        }

        const result = await this.savePersonnelProfileV2(params)
        this.$message.success(result.message)
        this.refresh()
      } catch (error) {
        this.$message.error(error.message)
      } finally {
        this.customField.isSubmitting = false
      }
    },

    async saveFamilyMember(doRefresh = true) {
      try {
        this.familyMember.isSubmitting = true
        const familyMember = JSON.stringify(this.buildFamilyMemberParams())
        const params = {
          user_id: this.userID,
          field: JSON.stringify({ [fieldID.FAMILY_MEMBER_ID]: familyMember })
        }
        const result = await this.savePersonnelProfileV2(params)
          .catch(err => {
            throw new Error('修改家庭情况失败', err)
          })

        if (result.code !== 200) {
          throw new Error(result.message ?? '')
        }

        this.familyMember.isSubmitting = false

        if (doRefresh) { await this.refresh() }

        this.$message.success('保存成功')
      } catch (e) {
        this.familyMember.isSubmitting = false
        this.$message.error(e.message)
      }
    },
    async saveCertList(doRefresh = true) {
      try {
        this.certList.isSubmitting = true
        const certList = JSON.stringify(this.buildCertParams())
        const params = {
          user_id: this.userID,
          field: JSON.stringify({ [fieldID.CERTIFICATE_ID]: certList })
        }
        const result = await this.savePersonnelProfileV2(params)
        this.certList.isSubmitting = false

        if (result.code !== 200) {
          throw new Error(result.message ?? '')
        }

        if (doRefresh) { await this.refresh() }

        this.$message.success('保存成功')
      } catch (e) {
        this.certList.isSubmitting = false
        this.$message.error(e.message)
      }
    },
    async saveWorkExp(doRefresh = true) {
      try {
        this.workExperience.isSubmitting = true
        const workExperience = JSON.stringify(this.buildWorkParams())
        const params = {
          user_id: this.userID,
          field: JSON.stringify({ [fieldID.WORK_EXP_ID]: workExperience })
        }
        const result = await this.savePersonnelProfileV2(params)
          .catch(err => {
            throw new Error('修改工作经历失败', err)
          })

        if (result.code !== 200) {
          throw new Error(result.message ?? '')
        }

        this.workExperience.isSubmitting = false

        if (doRefresh) { await this.refresh() }

        this.$message.success('保存成功')
      } catch (e) {
        this.workExperience.isSubmitting = false
        this.$message.error(e.message)
      }
    },
    async saveEduExp(doRefresh = true) {
      try {
        this.educationalExperience.isSubmitting = true
        const eduExp = JSON.stringify(this.buildEduExpParams())
        const params = {
          user_id: this.userID,
          field: JSON.stringify({ [fieldID.EDU_EXP_ID]: eduExp })
        }
        const result = await this.savePersonnelProfileV2(params)
          .catch(err => {
            throw new Error('修改工作经历失败', err)
          })

        if (result.code !== 200) {
          throw new Error(result.message ?? '')
        }

        this.educationalExperience.isSubmitting = false

        if (doRefresh) { await this.refresh() }

        this.$message.success('保存成功')
      } catch (e) {
        this.educationalExperience.isSubmitting = false
        this.$message.error(e.message)
      }
    },

    // params构建

    buildFamilyMemberParams() {
      return this.employeeDetails.draft.familyMembers.map(item => {
        const { name, relationship, age, workplace, political, career, phone } = item
        return {
          member: name,
          relationship,
          age,
          work_unit: workplace,
          political_outlook: political,
          occupations: career,
          phone
        }
      })
    },
    buildWorkParams() {
      return this.employeeDetails.draft.workExperience.map(item => {
        const {
          companyName,
          beginDate,
          endDate,
          department,
          post,
          reasonForLeaving,
          companyPhone,
          salary,
          scopeOfWork
        } = item
        return {
          companyName,
          beginDate: this.dateFormatter(beginDate),
          endDate: this.dateFormatter(endDate),
          reason_leaving: reasonForLeaving,
          department,
          position: post,
          company_telephone: companyPhone,
          salary,
          jobDescription: scopeOfWork
        }
      })
    },

    buildEduExpParams() {
      return this.employeeDetails.draft.educationalExperience.map(item => {
        const { schoolName, schoolType, major, beginDate, endDate, certificate, certificateNo } = item
        return {
          schoolName,
          beginDate: this.dateFormatter(beginDate),
          endDate: this.dateFormatter(endDate),
          major,
          certificate_number: certificateNo,
          certificate,
          schoolType: schoolType
        }
      })
    },
    buildCertParams() {
      return this.employeeDetails.draft.certificateList.map(item => {
        const { name, expireDate, attachment } = item
        return {
          name,
          expire_at: dayjs(expireDate).format('YYYY-MM-DD'),
          attachment: attachment
        }
      })
    },

    buildEmployeeProfileParamsV2() {
      const data = cloneDeep(this.employeeDetails.draft)
      data.certificateList = JSON.stringify(this.buildCertParams())
      data.educationalExperience = JSON.stringify(this.buildEduExpParams())
      data.workExperience = JSON.stringify(this.buildWorkParams())
      data.familyMembers = JSON.stringify(this.buildFamilyMemberParams())
      const params = {}
      for (const [key, fieldCfg] of this.fieldCfgs.byField) {
        if (fieldCfg['ofTable'] === 'user_details') {
          const mapTo = fieldCfg['mapTo']
          let result = data[key] ? data[key] : this.employeeDetails.backup[key]
          // console.log('this.employeeDetails.backup[key] --------->', this.employeeDetails.backup[key])
          console.log('result --------->', result)
          if (typeof fieldCfg['serialize'] === 'function') {
            result = fieldCfg['serialize'].apply(this, [fieldCfg, result])
          }
          const field = this.fieldList.find(field => field.field === mapTo)
          if (field) {
            params[field.id] = result
          }
          // params[mapTo] = result
        }
      }
      console.log(params, 'params')
      return params
    },

    buildCompanyProfileParamsV2() {
      const data = cloneDeep(this.companyDetails.draft)
      const params = {}
      for (const [key, fieldCfg] of this.fieldCfgs.byField) {
        if (fieldCfg['ofTable'] === 'user_companys') {
          const mapTo = fieldCfg['mapTo']
          let result = data[key]
          if (typeof fieldCfg['serialize'] === 'function') {
            result = fieldCfg['serialize'].apply(this, [fieldCfg, result])
          }
          const field = this.fieldList.find(field => field.field === mapTo)
          if (field) {
            params[field.id] = result
          }
        }
      }

      return params
    },

    buildOtherProfileParams() {
      const data = cloneDeep(this.customField.draft)
      const params = {}
      for (const [key, value] of Object.entries(data)) {
        let result = value
        const fieldCfg = this.customField.fieldConfig.get(key)

        if (fieldCfg.type === 'date') {
          result = this.dateFormatter(result)
        }

        params[fieldCfg.id] = result
      }

      return params
    },

    buildEmployeeProfileParams() {
      const {
        id,
        name,
        age,
        birthday,
        educationLevel,
        gender,
        idNo,
        domicile,
        nation,
        currentAddress,
        phone,
        email,
        marriageStatus,
        height,
        weight,
        oneInchPhoto,
        registeredResidenceType,
        idPeriodOfValidity,
        educationType,
        school,
        graduationDate,
        major,
        speciality,
        bankAccountNumber,
        bank,
        socialSecurityNumber,
        politicalStatus,
        backOfIDCard,
        frontOfIDCard,
        resumeAttachment,
        emergencyContact: ec,
        homePhone,
        computerSkills
      } = this.employeeDetails.draft

      let domicile_id
      const area = last(domicile)
      if (atLeast(area, ['label', 'value'])) { domicile_id = area.value }

      const result = {
        id,
        name,
        age,
        birthday_at: this.dateFormatter(birthday),
        education_id: educationLevel,
        gender,
        identiry_card: idNo,
        domicile_id,
        nation_id: nation,
        present_address: currentAddress,
        phone,
        family_phone: homePhone,
        email,
        marital_id: marriageStatus,
        height,
        weight,
        one_inch_photo: oneInchPhoto,
        registered_residence: registeredResidenceType,
        identity_card_at: this.dateFormatter(idPeriodOfValidity),
        education_nature: educationType,
        school_id: school?.value,
        graduation_at: this.dateFormatter(graduationDate),
        major,
        speciality,
        bank_card: bankAccountNumber,
        bank_id: bank?.value,
        social_insurance: socialSecurityNumber,
        politic_id: politicalStatus,
        identity_card_front: frontOfIDCard,
        identity_card_reverse: backOfIDCard,
        resume_attachment: resumeAttachment,
        computer_power: computerSkills
      }

      if (atLeast(ec, ['name', 'contact', 'relationship'])) {
        result.emergency_contact = JSON.stringify({
          name: ec.name,
          relation: ec.relationship,
          phone: ec.contact
        })
      }

      return result
    },
    buildCompanyArchiveParams() {
      const {
        id,
        employeeNumber,
        post,
        employeeType,
        entryDate,
        department,
        status,
        practiceBeginDate,
        practiceEndDate,
        dateOfbecomeARegularWorker,
        leader,
        salaryOfPractice,
        regularSalary,
        salary,
        laborContract,
        laborContractBeginDate,
        laborContractEndDate,
        departDate,
        entryMethod,
        reasonForLeaving,
        entryCount,
        apartment,
        physicalExamRecord,
        departSalaryStatus,
        temporaryResidencePermit,
        introducer
        // roles

      } = this.companyDetails.draft

      const result = {
        id,
        no: employeeNumber,
        identity: employeeType,
        entry_at: this.dateFormatter(entryDate),
        department_id: department,
        position_id: post?.value,
        job_status: status,
        practice_start_at: this.dateFormatter(practiceBeginDate),
        practice_end_at: this.dateFormatter(practiceEndDate),
        regular_at: this.dateFormatter(dateOfbecomeARegularWorker),
        leader_id: leader?.value,
        paractice_salary: salaryOfPractice,
        regular_salary: regularSalary,
        current_salary: salary ? salary.toFixed(2) : 0,
        labor_contract: laborContract,
        labor_contract_start: this.dateFormatter(laborContractBeginDate),
        labor_contract_end: this.dateFormatter(laborContractEndDate),
        quit_at: this.dateFormatter(departDate),
        entry_mode: entryMethod,
        quit_reason: reasonForLeaving,
        entry_number: entryCount,
        room_id: apartment?.value,
        physical_examination: physicalExamRecord,
        quit_salary_status: departSalaryStatus,
        temporary_residence_permit: temporaryResidencePermit,
        introducer_id: introducer

      }

      return result
    },
    dateFormatter(date) {
      if (!date) return null
      return dayjs(date).format('YYYY-MM-DD')
    },
    handleUploadResult(e) {
      this.uploadDialog.result = e
    },
    // ------------------
    editProfile() {
      this.employeeDetails.backup = cloneDeep(this.employeeDetails.draft)
      this.companyDetails.backup = cloneDeep(this.companyDetails.draft)
      this.customField.backup = cloneDeep(this.customField.draft)

      this.isEditing = true
    },
    undo() {
      this.isEditing = false
      this.employeeDetails.draft = this.employeeDetails.backup
      this.employeeDetails.backup = null

      this.companyDetails.draft = this.companyDetails.backup
      this.companyDetails.backup = null

      this.customField.draft = this.customField.backup
      this.customField.backup = null
    },

    uploadFile(type) {
      this.uploadDialog = {
        type,
        result: null,
        visible: true
      }
    },
    closeUploadDialog() {
      this.uploadDialog = {
        type: null,
        result: null,
        visible: false
      }
    },

    otherProfileUploadSuccess(e) {
      const { field, value } = e
      this.customField.draft[field] = value
    },

    uploadDialogConfirm() {
      switch (this.uploadDialog.type) {
        case 'resumeAttachment':
          this.employeeDetails.draft.resumeAttachment = value(this.uploadDialog.result, 'path', null)
          break

        case 'laborContract':
          this.companyDetails.draft.laborContract = value(this.uploadDialog.result, 'path', null)
          break

        case 'physicalExamRecord':
          this.companyDetails.draft.physicalExamRecord = value(this.uploadDialog.result, 'path', null)
          break

        case 'temporaryResidencePermit':
          this.companyDetails.draft.temporaryResidencePermit = value(this.uploadDialog.result, 'path', null)
          break

        case 'introducer':
          this.companyDetails.draft.introducer = value(this.uploadDialog.result, 'path', null)
          break

        case 'oneInchPhoto':
          this.employeeDetails.draft.oneInchPhoto = value(this.uploadDialog.result, 'path', null)
          break

        default:
          return
      }
      this.closeUploadDialog()
    },
    handleIDCardUploadResult(data, type) {
      switch (type) {
        case 'front':
          this.updateIDCardDialog.idcardFrontCache = data
          break

        case 'back':
          this.updateIDCardDialog.idcardBackCache = data
          break
      }
    },
    handleIDCardUploadConfirm() {
      if (this.updateIDCardDialog.applyToProfile) {
        const valid_to = value(this.updateIDCardDialog, 'idcardBackCache.analysis.result.valid_to', null)
        if (valid_to !== null) {
          this.employeeDetails.draft.idPeriodOfValidity = dayjs(valid_to).toDate()
        }

        const idNo = value(this.updateIDCardDialog, 'idcardFrontCache.analysis.result.number', null)
        if (isString(idNo) && idNo.trim() !== '') {
          this.employeeDetails.draft.idNo = idNo
        }

        const name = value(this.updateIDCardDialog, 'idcardFrontCache.analysis.result.name', null)
        if (isString(name) && name.trim() !== '') {
          this.employeeDetails.draft.name = name
        }

        const birth = value(this.updateIDCardDialog, 'idcardBackCache.analysis.result.birth', null)
        if (birth !== null) {
          this.employeeDetails.draft.birthday = dayjs(birth).toDate()
        }
      }

      this.employeeDetails.draft.backOfIDCard = value(this.updateIDCardDialog.idcardBackCache, 'path', null)
      this.employeeDetails.draft.frontOfIDCard = value(this.updateIDCardDialog.idcardFrontCache, 'path', null)

      this.updateIDCardDialog.visible = false
    },
    async downloadProfile() {
      try {
        this.exportProfile.loading = true

        const params = {
          user_id: this.userID
        }

        const result = await exportEntry(params)
          .catch(err => {
            throw new Error('导出档案失败', err)
          })

        if (
          result.code !== 200 ||
                    (isString(result, 'data.path') || result.data.path.trim() === '')
        ) { throw new Error(value(result, 'message', '导出档案失败')) }

        window.location.href = result.data.path
        this.exportProfile.loading = false
      } catch (e) {
        this.exportProfile.loading = false
        this.$message.error(e.message)
      }
    },
    // --------- 获取数据 ---------
    async getProfile() {
      const result = await getUser(this.userID)
        .catch(err => {
          throw new Error('获取用户档案失败', err)
        })

      if (result.code !== 200) { throw new Error(value(result, 'message', '获取用户档案失败')) }
    },
    async getProfileV2() {
      const result = await getPersonnelDetails({ user_id: this.userID })
        .catch(err => {
          throw new Error('获取用户档案失败', err)
        })

      if (result.code !== 200) { throw new Error(value(result, 'message', '获取用户档案失败')) }

      this.rawProfileData = result.data
    },

    async getFieldList() {
      const table = ['user_details', 'user_companys']
      const result = await getFieldsList({ table: JSON.stringify(table) })
        .catch(err => {
          throw new Error('获取字段列表失败', err)
        })
      this.fieldList = result.data
    },

    async getSchools() {
      const result = await getSchool()
        .catch(err => {
          throw new Error('获取学校选项失败', err)
        })

      if (result.code !== 200 || !Array.isArray(result.data)) { throw new Error(value(result, 'message', '获取学校选项失败')) }

      this.schools = result.data
    },
    async getNations() {
      const result = await getNation()
        .catch(err => {
          throw new Error('获取民族选项失败', err)
        })

      if (result.code !== 200 || !Array.isArray(result.data)) { throw new Error(value(result, 'message', '获取婚姻状态选项失败')) }

      this.nations = result.data
    },
    async getMarriageStatuses() {
      const result = await getMarriage()
        .catch(err => {
          throw new Error('获取婚姻状态选项失败', err)
        })

      if (result.code !== 200 || !Array.isArray(result.data)) { throw new Error(value(result, 'message', '获取婚姻状态选项失败')) }

      this.marriageStatuses = result.data
    },
    async getPolitics() {
      const result = await getPolitic()
        .catch(err => {
          throw new Error('获取政治面貌选项失败', err)
        })

      if (result.code !== 200 || !Array.isArray(result.data)) { throw new Error(value(result, 'message', '获取政治面貌选项失败')) }

      this.politics = result.data
    },
    async getPosts() {
      const result = await getPosition()
        .catch(err => {
          throw new Error('获取岗位信息失败', err)
        })

      if (result.code !== 200 || !Array.isArray(result.data)) { throw new Error(value(result, 'message', '获取岗位信息失败')) }

      this.posts = result.data
    },
    async getEducationalLevel() {
      const result = await getEducation()
        .catch(err => {
          throw new Error('获取学历选项失败', err)
        })

      if (result.code !== 200 || !Array.isArray(result.data)) { throw new Error(value(result, 'message', '获取学历选项失败')) }

      this.educationalLevel = result.data
    },

    async loadData() {
      const tasks = await Promise.allSettled([
        // this.getProfile(),
        this.getProfileV2(),
        this.getPosts(),
        this.getEducationalLevel(),
        this.getNations(),
        this.getPolitics(),
        this.getMarriageStatuses(),
        this.getFieldList()
        // this.getSchools()
      ])

      const failTasks = tasks.filter(task => task.status === 'rejected')

      if (failTasks.length > 0) {
        throw new Error(failTasks[0].reason)
      }
    },
    async initData() {
      try {
        this.isLoading = true
        await this.loadData()
        this.build()
        this.isLoading = false
      } catch (error) {
        this.isLoading = false
        this.$message.error(error.message ?? '加载数据时出现异常')
      }
    },
    async init() {
      this.userID = parseInt(this.$route.params?.id) || null
      this.initFields()
      await this.initData()
    }
  }
}
</script>

<template>
  <div v-loading="isLoading" class="app-container personal-profile-container">
    <!-- 修改记录 -->
    <el-card shadow="hover">
      <FieldsModifyHistory :user-i-d="userID" />
    </el-card>

    <!-- 员工档案 -->
    <el-card shadow="hover">
      <EmployeeArchives
        :profile="employeeDetails.draft"
        :is-editing="isEditing"
        :is-submitting="employeeDetails.isSubmitting"
        :educational_level_options="educationalLevelOptions"
        :marriage_statuses_options="marriageStatusesOptions"
        :politics_options="politicsOptions"
        :nation_options="nationOptions"
        @updateIDCard="updateIDCardDialog.visible = true"
        @uploadFile="uploadFile"
      >
        <template #extra>
          <el-button :loading="exportProfile.loading" size="small" @click="downloadProfile">
            下载申请表
          </el-button>
          <el-button v-if="isEditing" size="small" type="primary" plain @click="undo">
            取消
          </el-button>
          <template v-else>
            <el-button type="primary" size="small" @click="refresh">刷新</el-button>
            <el-button size="small" @click="editProfile">编辑</el-button>
          </template>
          <el-button
            v-if="isEditing"
            size="small"
            type="success"
            :loading="employeeDetails.isSubmitting || isSubmitting"
            @click="saveAll"
          >
            保存
          </el-button>
        </template>
      </EmployeeArchives>
    </el-card>

    <!-- 公司档案 -->
    <el-card shadow="hover">
      <CompanyArchives
        :profile="companyDetails.draft"
        :is-editing="isEditing"
        :is-submitting="companyDetails.isSubmitting"
        :user-i-d="userID"
        @uploadFile="uploadFile"
        @save="saveCompanyProfile"
      />
    </el-card>

    <!-- 其他档案 -->
    <el-card shadow="hover">
      <OtherArchives
        :is-submitting="customField.isSubmitting"
        :is-editing="isEditing"
        :profile="customField.draft"
        :field-config="customFieldsFormatter"
        @save="saveOtherProfile"
        @uploadSuccess="otherProfileUploadSuccess"
      />
    </el-card>

    <!-- 工作经历 -->
    <el-card shadow="hover">
      <WorkExperience
        v-model="employeeDetails.draft.workExperience"
        :is-editing="isEditing"
        :is-submitting="workExperience.isSubmitting"
        @save="saveWorkExp"
      />
    </el-card>

    <!-- 教育经历 -->
    <el-card shadow="hover">
      <EducationalExperience
        v-model="employeeDetails.draft.educationalExperience"
        :is-editing="isEditing"
        :is-submitting="educationalExperience.isSubmitting"
        @save="saveEduExp"
      />
    </el-card>

    <!-- 家庭成员 -->
    <el-card shadow="hover">
      <FamilyMember
        v-model="employeeDetails.draft.familyMembers"
        :is-submitting="familyMember.isSubmitting"
        :is-editing="isEditing"
        @save="saveFamilyMember"
      />
    </el-card>

    <!-- 证书 -->
    <el-card shadow="hover">
      <Certificate
        v-model="employeeDetails.draft.certificateList"
        :is-editing="isEditing"
        :is-submitting="certList.isSubmitting"
        @save="saveCertList"
      />
    </el-card>

    <!-- 签署协议 -->
    <el-card shadow="hover">
      <SignedAgreements :is-editing="isEditing" :user-i-d="userID" />
    </el-card>

    <!-- 培训课程 -->
    <el-card shadow="hover">
      <Courses :user-i-d="userID" :is-editing="isEditing" />
    </el-card>

    <!-- 修改身份证 -->
    <el-dialog
      title="修改身份证"
      :visible.sync="updateIDCardDialog.visible"
      width="30%"
    >
      <div>
        <SingleImage
          v-if="updateIDCardDialog.visible"
          idcard
          @input="handleIDCardUploadResult"
        />
        <el-checkbox v-model="updateIDCardDialog.applyToProfile" style="margin-top: 10px">
          保存到档案
        </el-checkbox>
      </div>
      <template #footer>
        <el-button @click="updateIDCardDialog.visible = false">取 消</el-button>
        <el-button type="primary" @click="handleIDCardUploadConfirm">确 定</el-button>
      </template>
    </el-dialog>

    <!-- 上传 -->
    <el-dialog title="上传" width="30%" :visible.sync="uploadDialog.visible">
      <SingleImage
        v-if="uploadDialog.visible"
        allow-file
        @input="handleUploadResult"
      />
      <template #footer>
        <el-button @click="closeUploadDialog">取 消</el-button>
        <el-button type="primary" @click="uploadDialogConfirm">确 定</el-button>
      </template>
    </el-dialog>
  </div>
</template>

<style lang="scss">
.personal-profile-container {
  background-color: #f5f5f5;
  padding: 20px;

  .el-card {
    margin-bottom: 20px;
    border-radius: 8px;
    overflow: hidden;

    &:last-child {
      margin-bottom: 0;
    }
  }
}
</style>

